home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 5 / Apprentice-Release5.iso / Source Code / Libraries / DCLAP 6d / dclap6d / SeqPups / appsrc / drawtree.src / drawgraphics.c < prev    next >
C/C++ Source or Header  |  1996-07-05  |  58KB  |  2,312 lines

  1. #include "drawgraphics.h"
  2.  
  3. #ifdef QUICKC
  4. struct videoconfig myscreen;
  5. void   setupgraphics();
  6. #endif
  7.  
  8. Static colortype colors[7] = {
  9.   {"White    ",0.9,0.9,0.9},
  10.   {"Red      ",1.0,0.3,0.3},
  11.   {"Orange   ",1.0,0.6,0.6},
  12.   {"Yellow   ",1.0,0.9,0.4},
  13.   {"Green    ",0.3,0.8,0.3},
  14.   {"Blue     ",0.5,0.5,1.0},
  15.   {"Violet   ",0.6,0.4,0.8},
  16. };
  17.  
  18. /*
  19.  * Used ONLY here: */
  20.  
  21. static long eb[]={
  22.   0 , 1 ,2 ,3 ,55,45,46,47,22,5,37,11,12,13,14,15,16,17,18,19,60,61,50,38,
  23.   24, 25,63,39,28,29,30,31,64,90,127,123,91,108,80,125,77,93,92,78,107,96,
  24.   75,97,240,241,242,243,244,245,246,247,248,249,122,94,76,126,110,111, 124,
  25.   193,194,195,196,197,198,199,200,201,209,210,211, 212,213,214,215,216,217,
  26.   226,227,228,229,230,231,232,233,173,224,189, 95,109,121,129,130,131,132,
  27.   133,134,135,136,137,145,146,147,148,149,150, 151, 152,153,162,163,164,165,
  28.   166,167,168,169,192,79,208,161,7};
  29.  
  30. long   hpresolution,nmoves,oldpictint,oldx,oldy;
  31. double  labelline,linewidth,oldxhigh,oldxlow,oldyhigh,oldylow,oldxreal,
  32.         oldyreal,raylinewidth,treeline,oldxsize,oldysize,oldxunitspercm,
  33.         oldyunitspercm,oldxcorner,oldycorner;
  34. long rootmatrix[51][51];
  35. long  HiMode,GraphDriver,GraphMode,LoMode;
  36. boolean didenter,didexit,didcompute;
  37.  
  38. long    bytewrite = 0;
  39.  
  40. /* externals will move to .h file later. */
  41. extern long         strpbottom,strptop,strpwide,strpdeep,strpdiv;
  42. extern boolean       dotmatrix,empty,preview,previewing;
  43. extern double        expand,xcorner,xnow,xsize,xscale,xunitspercm,
  44.                                       ycorner,ynow,ysize,yscale,yunitspercm,
  45.                                       labelheight,ymargin;
  46. extern long          filesize;
  47. extern growth        grows;
  48. extern enum {yes,no} penchange,oldpenchange;
  49. extern FILE          *plotfile;
  50. extern plottertype   plotter,oldplotter,previewer;
  51. extern striptype     stripe;
  52.  
  53. extern char pltfilename[100];
  54.  
  55. void pout(n)
  56. long n;
  57. {
  58. #ifdef MAC
  59.   if (previewing)
  60.     printf("%*ld", (int)((long)(0.434295 * log((double)n) + 0.0001)), n);
  61.   else
  62.     fprintf(plotfile, "%*ld",
  63.         (int)((long)(0.434295 * log((double)n) + 0.0001)), n);
  64. #else
  65.   if (previewing)
  66.     printf("%*d", (int)((long)(0.434295 * log((double)n) + 0.0001)), n);
  67.   else
  68.     fprintf(plotfile, "%*d",
  69.             (int)((long)(0.434295 * log((double)n) + 0.0001)), n);
  70. #endif
  71. }  /* pout */
  72.  
  73.  
  74. long upbyte(num)
  75. long num;
  76. {
  77.   /* get upper nibble of byte */
  78.   long Result, i, j, bytenum, nibcount;
  79.   boolean done;
  80.  
  81.   bytenum = 0;
  82.   done = false;
  83.   nibcount = 0;
  84.   i = num / 16;
  85.   i /= 16;
  86.   j = 1;
  87.   while (!done) {
  88.     bytenum += (i & 15) * j;
  89.     nibcount++;
  90.     if (nibcount == 2) {
  91.       Result = bytenum;
  92.       done = true;
  93.     } else {
  94.       j *= 16;
  95.       i /= 16;
  96.     }
  97.   }
  98.   return Result;
  99. }  /* upbyte */
  100.  
  101.  
  102.  
  103. Local long lobyte(num)
  104. long num;
  105. {
  106.   /* get low order nibble of byte */
  107.   long Result, i, j, bytenum, nibcount;
  108.   boolean done;
  109.  
  110.   bytenum = 0;
  111.   done = false;
  112.   nibcount = 0;
  113.   i = num;
  114.   j = 1;
  115.   while (!done) {
  116.     bytenum += (i & 15) * j;
  117.     nibcount++;
  118.     if (nibcount == 2) {
  119.       Result = bytenum;
  120.       done = true;
  121.     } else {
  122.       j *= 16;
  123.       i /= 16;
  124.     }
  125.   }
  126.   return Result;
  127. }  /* lobyte */
  128.  
  129.  
  130. void plotdot(ix, iy)
  131. long ix, iy;
  132. {
  133.   /* plot one dot at ix, iy */
  134.   long ix0, iy0, iy1, iy2;
  135.  
  136.   iy0 = strptop - iy;
  137.   if ((unsigned)iy0 > strpdeep || ix <= 0 || ix > strpwide)
  138.     return;
  139.   empty = false;
  140.   ix0 = ix;
  141.   switch (plotter) {
  142.  
  143.   case citoh:
  144.     iy1 = 1;
  145.     iy2 = iy0;
  146.     break;
  147.  
  148.   case epson:
  149.     iy1 = 1;
  150.     iy2 = 7 - iy0;
  151.     break;
  152.  
  153.   case oki:
  154.     iy1 = 1;
  155.     iy2 = 7 - iy0;
  156.     break;
  157.  
  158.   case toshiba:
  159.     iy1 = iy0 / 6 + 1;
  160.     iy2 = 5 - iy0 % 6;
  161.     break;
  162.  
  163.   case pcx:
  164.     iy1 = iy0 + 1;
  165.     ix0 = (ix - 1) / 8 + 1;
  166.     iy2 = 7 - ((ix - 1) & 7);
  167.     break;
  168.  
  169.   case pcl:
  170.     iy1 = iy0 + 1;
  171.     ix0 = (ix - 1) / 8 + 1;
  172.     iy2 = 7 - ((ix - 1) & 7);
  173.     break;
  174.  
  175.   case xbm:
  176.     iy1 = iy0 + 1;
  177.     ix0 = (ix - 1) / 8 + 1;
  178.     iy2 = (ix - 1) & 7;
  179.     break;
  180.  
  181.   case other:
  182.     break;
  183.     /* code for making dot array for a new printer
  184.       goes here */
  185.   }
  186.   stripe[iy1 - 1][ix0 - 1] |= (unsigned char)1<<iy2;
  187. }  /* plotdot */
  188.  
  189.  
  190.  
  191. void drawpen(x, y, width)
  192. long x, y, width;
  193. {
  194.   long i, j, radius, low, hi;
  195.  
  196.   radius = (long)floor(width / 2.0 + 0.5);
  197.   low = (long)floor(0.5 - width / 2.0);
  198.   hi = width - low;
  199.   if (y + hi < strpbottom || y + low > strptop) {
  200.     if (didenter)
  201.       didexit = true;
  202.     return;
  203.   }
  204.   if (!didenter)
  205.     didenter = true;
  206.   for (i = low; i <= hi; i++) {
  207.     for (j = low; j <= hi; j++) {
  208.       if (rootmatrix[abs(i)][abs(j)] <= radius){
  209.     plotdot(x + i, y + j);
  210.     plotdot(x + i, y - j);
  211.     plotdot(x - i, y + j);
  212.     plotdot(x - 1, y - j);}
  213.     }
  214.   }
  215. }  /* drawpen */
  216.  
  217.  
  218.  
  219.  
  220. void drawfatline(ixabs, iyabs, ixnow, iynow, penwide)
  221. long ixabs, iyabs, ixnow, iynow, penwide;
  222. {
  223.   long temp, xdiff, ydiff, err, x1, y1;
  224.  
  225.   didenter = false;
  226.   didexit = false;
  227.  
  228.   if (ixabs < ixnow) {
  229.     temp = ixnow;
  230.     ixnow = ixabs;
  231.     ixabs = temp;
  232.     temp = iynow;
  233.     iynow = iyabs;
  234.     iyabs = temp;
  235.   }
  236.   xdiff = ixabs - ixnow;
  237.   ydiff = iyabs - iynow;
  238.   if (ydiff >= 0) {
  239.     if (xdiff >= ydiff) {
  240.       err = -(xdiff / 2);
  241.       x1 = ixnow;
  242.       while (x1 <= ixabs && !(didenter && didexit)) {
  243.     drawpen(x1, iynow, penwide);
  244.     err += ydiff;
  245.     if (err > 0) {
  246.       iynow++;
  247.       err -= xdiff;
  248.     }
  249.     x1++;
  250.       }
  251.       return;
  252.     }
  253.     err = -(ydiff / 2);
  254.     y1 = iynow;
  255.     while (y1 < iyabs && !(didenter && didexit)) {
  256.       drawpen(ixnow, y1, penwide);
  257.       err += xdiff;
  258.       if (err > 0) {
  259.     ixnow++;
  260.     err -= ydiff;
  261.       }
  262.       y1++;
  263.     }
  264.     return;
  265.   }
  266.   if (xdiff < -ydiff) {
  267.     err = ydiff / 2;
  268.     y1 = iynow;
  269.     while (y1 >= iyabs && !(didenter && didexit)) {
  270.       drawpen(ixnow, y1, penwide);
  271.       err += xdiff;
  272.       if (err > 0) {
  273.     ixnow++;
  274.     err += ydiff;
  275.       }
  276.       y1--;
  277.     }
  278.     return;
  279.   }
  280.   err = -(xdiff / 2);
  281.   x1 = ixnow;
  282.   while (x1 <= ixabs && !(didenter && didexit)) {
  283.     drawpen(x1, iynow, penwide);
  284.     err -= ydiff;
  285.     if (err > 0) {
  286.       iynow--;
  287.       err -= xdiff;
  288.     }
  289.     x1++;
  290.   }
  291. }  /* drawfatline */
  292.  
  293.  
  294. void plot(pen, xabs, yabs)
  295. pensttstype pen;
  296. double xabs, yabs;
  297. {
  298.   long xhigh, yhigh, xlow, ylow, newx, newy, ixnow, iynow, ixabs, iyabs,
  299.        ixleft, iyleft, ixbot, iybot, ixtop, iytop, cdx, cdy, temp;
  300.   long pictint;
  301.   double c, dx, dy, lscale, dxreal, dyreal;
  302.   Char picthi, pictlo;
  303. #ifdef MAC
  304.   queryevent();
  305. #endif
  306.   if (!dotmatrix || previewing) {
  307.     switch (plotter) {
  308.  
  309.     case tek:
  310.       if (pen == penup) {
  311.         if (previewing)
  312.           putchar('\035');
  313.         else
  314.           putc('\035', plotfile);
  315.       }
  316.       ixnow = (long)floor(xabs + 0.5);
  317.       iynow = (long)floor(yabs + 0.5);
  318.       xhigh = ixnow / 32;
  319.       yhigh = iynow / 32;
  320.       xlow = ixnow & 31;
  321.       ylow = iynow & 31;
  322.       if (!ebcdic) {
  323.         if (yhigh != oldyhigh) {
  324.           if (previewing)
  325.             putchar(yhigh + 32);
  326.           else
  327.             putc(yhigh + 32, plotfile);
  328.         }
  329.         if (ylow != oldylow || xhigh != oldxhigh) {
  330.           if (previewing)
  331.             putchar(ylow + 96);
  332.           else
  333.             putc(ylow + 96, plotfile);
  334.         }
  335.         if (xhigh != oldxhigh) {
  336.           if (previewing)
  337.             putchar(xhigh + 32);
  338.           else
  339.             putc(xhigh + 32, plotfile);
  340.         }
  341.         if (previewing)
  342.           putchar(xlow + 64);
  343.         else
  344.           putc(xlow + 64, plotfile);
  345.       } else {  /* DLS/JMH -- for systems that use EBCDIC coding */
  346.         if (yhigh != oldyhigh) {
  347.           if (previewing)
  348.             putchar(eb[yhigh + 32]);
  349.           else
  350.             putc(eb[yhigh + 32], plotfile);
  351.         }
  352.         if (ylow != oldylow || xhigh != oldxhigh) {
  353.           if (previewing)
  354.             putchar(eb[ylow + 96]);
  355.           else
  356.             putc(eb[ylow + 96], plotfile);
  357.         }
  358.         if (xhigh != oldxhigh) {
  359.           if (previewing)
  360.             putchar(eb[xhigh + 32]);
  361.           else
  362.             putc(eb[xhigh + 32], plotfile);
  363.         }
  364.         if (previewing)
  365.           putchar(eb[xlow + 64]);
  366.         else
  367.           putc(eb[xlow + 64], plotfile);
  368.       }
  369.  
  370.       oldxhigh = xhigh;
  371.       oldxlow = xlow;
  372.       oldyhigh = yhigh;
  373.       oldylow = ylow;
  374.       break;
  375.  
  376.     case hp:
  377.       if (pen == pendown)
  378.         fprintf(plotfile, "PD");
  379.       else
  380.         fprintf(plotfile, "PU");
  381.       pout((long)floor(xabs + 0.5));
  382.       putc(',', plotfile);
  383.       pout((long)floor(yabs + 0.5));
  384.       fprintf(plotfile, ";\n");
  385.       break;
  386.  
  387.     case pict:
  388.       newx = (long)floor(xabs + 0.5);
  389.       newy = (long)floor(ysize * yunitspercm - yabs + 0.5);
  390.       if (pen == pendown) {
  391.         if (linewidth > 5) {
  392.           dxreal = xabs - oldxreal;
  393.           dyreal = yabs - oldyreal;
  394.           lscale = sqrt(dxreal * dxreal + dyreal * dyreal) /
  395.             (fabs(dxreal) + fabs(dyreal));
  396.           pictint = (long)(lscale * linewidth + 0.5);
  397.  
  398.           if (pictint == 0)
  399.             pictint = 1;
  400.           if (pictint != oldpictint) {
  401.             picthi = (Char)(pictint / 256);
  402.             pictlo = (Char)(pictint & 255);
  403.             fprintf(plotfile, "\007%c%c%c%c", picthi, pictlo, picthi, pictlo);
  404.             bytewrite+=5;
  405.           }
  406.           oldpictint = pictint;
  407.         }
  408.         fprintf(plotfile, " %c%c%c%c",
  409.                 (Char)(oldy / 256), (Char)(oldy & 255), (Char)(oldx / 256),
  410.                 (Char)(oldx & 255));
  411.         bytewrite+=5;
  412.  
  413.         fprintf(plotfile, "%c%c%c%c",
  414.                 (Char)(newy / 256), (Char)(newy & 255), (Char)(newx / 256),
  415.                 (Char)(newx & 255));
  416.         bytewrite+=5;
  417.         }
  418.       oldxreal = xabs;
  419.       oldyreal = yabs;
  420.       oldx = newx;
  421.       oldy = newy;
  422.  
  423.       break;
  424. #ifndef MAC
  425.     case ray:
  426.       if (pen == pendown) {
  427.         if (linewidth != treeline) {
  428.           if (raylinewidth > labelline) {
  429.             raylinewidth = labelline;
  430.             fprintf(plotfile, "end\n\n");
  431.             fprintf(plotfile, "name species_names\n");
  432.             fprintf(plotfile, "grid 22 22 22\n");
  433.           }
  434.         }
  435.  
  436.         if (oldxreal != xabs || oldyreal != yabs) {
  437.           raylinewidth *= 0.99999;
  438.           fprintf(plotfile, "cylinder %8.7f %6.3f 0 %6.3f %6.3f 0 %6.3f\n",
  439.                   raylinewidth, oldxreal, oldyreal, xabs, yabs);
  440.           fprintf(plotfile, "sphere %8.7f %6.3f 0 %6.3f\n",
  441.                   raylinewidth, xabs, yabs);
  442.         }
  443.       }
  444.       oldxreal = xabs;
  445.       oldyreal = yabs;
  446.       break;
  447. #endif /* ifndef MAC */
  448.     case lw:
  449.       if (pen == pendown)
  450.         fprintf(plotfile, "%8.2f%8.2f lineto\n", xabs, yabs);
  451.       else
  452.         fprintf(plotfile, "stroke %8.2f%8.2f moveto\n", xabs, yabs);
  453.       break;
  454.  
  455.     case ibmpc:
  456. #ifdef TURBOC
  457.     newx =  (long)(floor(xabs + 0.5));
  458.     newy = abs((long)(floor(yabs)) - getmaxy());
  459.     if (pen == pendown)
  460.         line(oldx,oldy,newx,newy);
  461.     oldx=newx;
  462.     oldy=newy;
  463. #endif
  464. #ifdef QUICKC
  465.     newx =  (long)(floor(xabs + 0.5));
  466.     newy = abs((long)(floor(yabs)) - myscreen.numypixels);
  467.  
  468.     if (pen == pendown)
  469.         _lineto((long)newx,(long)newy);
  470.     else
  471.         _moveto((long)newx,(long)newy);
  472.     oldx=newx;
  473.     oldy=newy;
  474.  
  475. #endif
  476.     break;
  477.      case mac:
  478. #if defined(MAC)  || defined(__MWERKS__)
  479.       if (pen == pendown){
  480.     LineTo((int)floor((double)xabs + 0.5),
  481.            342 - (long)floor((double)yabs + 0.5));}
  482.       else{
  483.     MoveTo((int)floor((double)xabs + 0.5),
  484.            342 - (long)floor((double)yabs + 0.5));}
  485. #endif
  486.  
  487.       break;
  488.  
  489.     case houston:
  490.       if (pen == pendown)
  491.         fprintf(plotfile, "D ");
  492.       else
  493.         fprintf(plotfile, "U ");
  494.       pout((long)((long)floor(xabs + 0.5)));
  495.       putc(',', plotfile);
  496.       pout((long)((long)floor(yabs + 0.5)));
  497.       putc('\n', plotfile);
  498.       break;
  499.  
  500.     case decregis:
  501.       newx = (long)floor(xabs + 0.5);
  502.       newy = (long)abs((long)floor(yabs + 0.5) - 479);
  503.       if (pen == pendown) {
  504.         if (previewing) {
  505.           printf("P[");
  506.           pout(oldx);
  507.           putchar(',');
  508.           pout(oldy);
  509.           printf("]V[");
  510.           pout(newx);
  511.           putchar(',');
  512.           pout(newy);
  513.           putchar(']');
  514.         } else {
  515.           fprintf(plotfile, "P[");
  516.           pout(oldx);
  517.           putc(',', plotfile);
  518.           pout(oldy);
  519.           fprintf(plotfile, "]V[");
  520.           pout(newx);
  521.           putc(',', plotfile);
  522.           pout(newy);
  523.           putc(']', plotfile);
  524.         }
  525.         nmoves++;
  526.         if (nmoves == 3) {
  527.           nmoves = 0;
  528.           if (previewing)
  529.             putchar('\n');
  530.           else
  531.             putc('\n', plotfile);
  532.         }
  533.       }
  534.       oldx = newx;
  535.       oldy = newy;
  536.       break;
  537.  
  538.     case fig:
  539.       newx = (long)floor(xabs + 0.5);
  540.       newy = (long)floor(yabs + 0.5);
  541.       if (pen == pendown) {
  542.     fprintf(plotfile, "2 1 0 %5ld 0 0 0 0 0.000 0 0\n",
  543.         (long)floor(linewidth + 0.5) + 1);
  544.     fprintf(plotfile, "%5ld%5ld%5ld%5ld 9999 9999\n",
  545.         oldx, 606 - oldy, newx, 606 - newy);
  546.  
  547.     fprintf(plotfile,
  548.       "1 3 0  1 0 0 0 21 0.00 1 0.0 %5ld%5ld%5ld %5ld %5ld%5ld%5ld 349\n",
  549.       oldx, 606 - oldy, (long)floor(linewidth / 2 + 0.5),
  550.       (long)floor(linewidth / 2 + 0.5), oldx, 606 - oldy, 606 - oldy);
  551.     fprintf(plotfile,
  552.       "1 3 0  1 0 0 0 21 0.00 1 0.0 %5ld%5ld%5ld %5ld %5ld%5ld%5ld 349\n",
  553.       newx, 606 - newy, (long)floor(linewidth / 2 + 0.5),
  554.       (long)floor(linewidth / 2 + 0.5), newx, 606 - newy, 606 - newy);
  555.  
  556.       }
  557.       oldx = newx;
  558.       oldy = newy;
  559.       break;
  560.     case other:
  561.       break;
  562.       /* code for a pen move on a new plotter goes here */
  563.     }
  564.     return;
  565.   }
  566.   if (pen == pendown) {
  567.     ixabs = (long)floor(xabs + 0.5);
  568.     iyabs = (long)floor(yabs + 0.5);
  569.     ixnow = (long)floor(xnow + 0.5);
  570.     iynow = (long)floor(ynow + 0.5);
  571.     if (ixnow > ixabs) {
  572.       temp = ixnow;
  573.       ixnow = ixabs;
  574.       ixabs = temp;
  575.       temp = iynow;
  576.       iynow = iyabs;
  577.       iyabs = temp;
  578.     }
  579.     dx = ixabs - ixnow;
  580.     dy = iyabs - iynow;
  581.    /* if (dx + fabs(dy) <= 0.0)
  582.       c = 0.0;
  583.     else
  584.       c = 0.5 * linewidth / sqrt(dx * dx + dy * dy); */
  585.     cdx = (long)floor(linewidth + 0.5);
  586.     cdy = (long)floor(linewidth + 0.5);
  587.     if ((iyabs + cdx >= strpbottom || iynow + cdx >= strpbottom) &&
  588.         (iyabs - cdx <= strptop || iynow - cdx <= strptop)) {
  589.       drawfatline(ixnow,iynow,ixabs,iyabs,(long)floor(linewidth+0.5));}
  590.   }
  591.  
  592.   xnow = xabs;
  593.   ynow = yabs;
  594.  
  595.   /* Bitmap Code to plot (xnow,ynow) to (xabs,yabs)                 */
  596. } /* plot                                                           */
  597.  
  598.  
  599. void pictoutint(file,pictint)
  600. FILE *file;
  601. long  pictint;
  602. {
  603. char picthi, pictlo;
  604.  
  605. picthi = (char)(pictint / 256);
  606. pictlo = (char)(pictint % 256);
  607. fprintf(file, "%c%c", picthi, pictlo);
  608. }
  609.  
  610. void initplotter(ntips,fontname)
  611. long ntips;
  612. char *fontname;
  613. {
  614.   long i,j, hres, vres;
  615.   Char picthi, pictlo;
  616.   long pictint;
  617.  
  618.   treeline = 0.18 * labelheight * yscale * expand;
  619.   labelline = 0.06 * labelheight * yscale * expand;
  620.   linewidth = treeline;
  621.   if (dotmatrix ) {
  622.     for (i = 0; i <= 50; i++) {   /* for fast circle calculations */
  623.      for (j = 0; j <= 50; j++){
  624.        rootmatrix[i][j] =
  625.        (long)floor(sqrt((double)(i * i + j * j)) + 0.5);}
  626.    }
  627.   }
  628.  bytewrite = 0;
  629.  switch (plotter) {
  630.  
  631.   case tek:
  632.     oldxhigh = -1.0;
  633.     oldxlow = -1.0;
  634.     oldyhigh = -1.0;
  635.     oldylow = -1.0;
  636.     nmoves = 0;       /* DLS/JMH -- See function  PLOT                  */
  637.     if (previewing)   /* DLS/JMH                                        */
  638.       printf("%c\f", escape);   /* DLS/JMH */
  639.     else
  640.       fprintf(plotfile, "%c\f", escape);
  641.     break;
  642.  
  643.   case hp:
  644.     fprintf(plotfile, "IN;SP1;VS10.0;\n");
  645.     break;
  646. #ifndef MAC
  647.   case ray:
  648.     treeline = 0.27 * labelheight * yscale * expand;
  649.     linewidth = treeline;
  650.     raylinewidth = treeline;
  651.     if (grows == vertical)
  652.       fprintf(plotfile, "plane backcolor 0 0 %2.4f 0 0 1\n", ymargin);
  653.     else
  654.       fprintf(plotfile, "plane backcolor 0 0 %2.4f 0 0 1\n",
  655.               ymargin - ysize / (ntips - 1));
  656.  
  657.     fprintf(plotfile, "\nname tree\n");
  658.     fprintf(plotfile, "grid 22 22 22\n");
  659.     break;
  660. #endif /* ifndef mac */
  661.  
  662.   case pict:
  663. #if 1
  664.     plotfile = freopen(pltfilename,"wb",plotfile);
  665.     for (i=0;i<512;++i)
  666.       putc('\000',plotfile);
  667.     pictoutint(plotfile,1000); /* size...replaced later with seek */
  668.     pictoutint(plotfile,1);    /* bbx0   */
  669.     pictoutint(plotfile,1);    /* bby0   */
  670.     pictoutint(plotfile,612);  /* bbx1   */
  671.     pictoutint(plotfile,792);  /* bby1   */
  672.     fprintf(plotfile,"%c%c",0x11,0x01); /* version "1" (B&W) pict */
  673.     fprintf(plotfile,"%c%c%c",0xa0,0x00,0x82);
  674.     fprintf(plotfile,"%c",1);    /* clip rect */
  675.     pictoutint(plotfile,10);  /* region size, bytes. */
  676.     pictoutint(plotfile,1);   /* clip x0             */
  677.     pictoutint(plotfile,1);   /* clip y0             */
  678.     pictoutint(plotfile,612); /* clip x1             */
  679.     pictoutint(plotfile,792); /* clip y1             */
  680.     
  681.     bytewrite+=543;
  682.  
  683.     oldpictint = 0;
  684.     pictint = (long)(linewidth + 0.5);
  685.     if (pictint == 0)
  686.       pictint = 1;
  687.     picthi = (Char)(pictint / 256);
  688.     pictlo = (Char)(pictint % 256);
  689.     fprintf(plotfile, "\007%c%c%c%c", picthi, pictlo, picthi, pictlo);
  690.     bytewrite+=5;
  691.     /* Set pen size for drawing tree. */
  692.     break;
  693. #else
  694.     plotfile = freopen(pltfilename,"wb",plotfile);
  695.     fprintf(plotfile, "DRW");
  696.     fprintf(plotfile, "GD2%c%c%c%c",0,6,0,3);
  697.     for (i = 1; i <= 3; i++)
  698.       putc('\000',plotfile);
  699.       putc(72,plotfile); putc(0,plotfile) ; putc(72,plotfile);
  700.     for (i = 1; i <= 4; i++)
  701.       putc(0,plotfile);
  702.     fprintf(plotfile, "\002\332\002(\377\341\377\342\002\371\002F\003g\005(");
  703.     fprintf(plotfile, "\003\374%c\002",0);
  704.     for (i = 1; i <= 3; i++)
  705.         putc('\000',plotfile);
  706.     fprintf(plotfile,"H%cH",0);
  707.  
  708.     for (i = 1; i <= 4; i++)
  709.         putc('\000',plotfile);
  710.     fprintf(plotfile, "\002\332\002");
  711.     putc(40,plotfile);
  712.     putc(0,plotfile);
  713.     putc(1,plotfile);
  714.     for (i = 1; i <= 3; i++)
  715.       putc('\000',plotfile);
  716.     putc('d', plotfile);
  717.     for (i = 1; i <= 3; i++)
  718.             putc('\000',plotfile);
  719.     fputc('\001',plotfile);
  720.     fputc('\000',plotfile);
  721.     fprintf(plotfile, "\001\001\001");
  722.     for (i = 1; i <= 3; i++)
  723.             putc('\000',plotfile);
  724.  
  725.     fprintf(plotfile, "\001'\017");
  726.     putc('\000',plotfile);
  727.     putc('\001',plotfile);
  728.     putc('\000',plotfile);
  729.     putc('\001',plotfile);
  730.     for (i = 1; i <= 13; i++)
  731.       putc('\000',plotfile);
  732.     putc('\002',plotfile);
  733.     putc('\000',plotfile);
  734.     fprintf(plotfile,"\031\001");
  735.     putc(144, plotfile);
  736.     for (i = 1; i <= 5; i++)
  737.       putc('\000',plotfile);
  738.     putc('@', plotfile);
  739.     for (i = 1; i <= 35; i++)
  740.       putc('\000',plotfile);
  741.     putc('H', plotfile);
  742.     for (i = 1; i <= 3; i++)
  743.       putc('\000',plotfile);
  744.     putc('H', plotfile);
  745.     for (i = 1; i <= 4; i++)
  746.       putc('\000',plotfile);
  747.     fprintf(plotfile, "\001%c\002\003",0);
  748.     fprintf(plotfile, "\002%c\003%c%c\001\003",0,0,0);
  749.     fprintf(plotfile, "\001\001%c%c",0,0);
  750.     fprintf(plotfile, "\001\001%c\001%c\002",0,0);
  751.     fprintf(plotfile, "\332\002(");
  752.     fprintf(plotfile, "\002\332\002(\002");
  753.     fprintf(plotfile, "\332\002(");
  754.     for (i = 1; i <= 5; i++)
  755.       putc('\000',plotfile);
  756.     fprintf(plotfile, "\001\001\001\006");
  757.     putc('\000',plotfile);
  758.     putc('\001', plotfile);
  759.     for (i = 1; i <= 323; i++)
  760.       putc('\000',plotfile);
  761.     fprintf(plotfile, "\002G%c\033",0);
  762.     fprintf(plotfile, "%c\020%c0%c",0,0,0);
  763.     fprintf(plotfile, "]\021\001");
  764.     fprintf(plotfile, "\240%c\202\001%c",0,0);
  765.     fprintf(plotfile, "\012%c\033%c",0,0);
  766.     fprintf(plotfile, "\020%c0%c",0,0);
  767.     putc(']', plotfile);
  768.     /* Take a moment here to appreciate the beauty of empirical methods. */
  769.     oldpictint = 0;
  770.     pictint = (long)(linewidth + 0.5);
  771.     if (pictint == 0)
  772.       pictint = 1;
  773.     picthi = (Char)(pictint / 256);
  774.     pictlo = (Char)(pictint & 255);
  775.     fprintf(plotfile, "\007%c%c%c%c", picthi, pictlo, picthi, pictlo);
  776.     /* Set pen size for drawing tree. */
  777. #endif
  778.     break;
  779.     
  780.   case xbm:  /* what a completely verbose data representation format.*/
  781.  
  782.     fprintf(plotfile, "#define drawgram_width %5ld\n",
  783.             (long)(xunitspercm * xsize));
  784.     fprintf(plotfile, "#define drawgram_height %5ld\n",
  785.             (long)(yunitspercm * ysize));
  786.     fprintf(plotfile, "static char drawgram_bits[] = {\n");
  787.     /*filesize := 53;  */
  788.     break;
  789.   case lw:     /* write conforming encapsulated postscript */
  790.     fprintf(plotfile, "%%!PS-Adobe-2.0 EPSF-2.0\n");
  791.     fprintf(plotfile,"%%%%Creator: Phylip\n");
  792.     fprintf(plotfile,"%%%%Title:  phylip.ps\n%%%%Pages: 1\n");
  793.     fprintf(plotfile,"%%%%BoundingBox: 0 0 612 792\n");
  794.     fprintf(plotfile,"%%%%EndComments\n%%%%EndProlog\n%%%%Page: 1 1\n\n");
  795.     fprintf(plotfile," 1 setlinecap \n 1 setlinejoin  \n");
  796.     fprintf(plotfile, "%8.2f setlinewidth newpath \n", treeline);
  797.     break;
  798.  
  799.   case ibmpc:
  800. #ifdef TURBOC
  801.     initgraph(&GraphDriver,&HiMode,"");
  802. #endif
  803. #ifdef QUICKC
  804.     setupgraphics();
  805. #endif
  806.     break;
  807.  
  808.   case mac:
  809. #if defined(MAC) || defined(__MWERKS__)
  810. #ifdef MAC
  811.     gfxmode();
  812. #endif
  813. #ifdef __MWERKS__
  814.     for (i=0; i<40; i++) printf("\n"); /* "clear" screen */
  815. #endif
  816.     pictint=(long)(linewidth + 0.5);
  817.     if (pictint == 0)
  818.          pictint=1;
  819.     PenSize((int)pictint,(int)pictint);
  820. #endif
  821.     break;
  822.  
  823.   case houston:
  824.     break;
  825.  
  826.   case decregis:
  827.     oldx = 300;
  828.     oldy = 1;
  829.     nmoves = 0;
  830.     if (previewing)
  831.       printf("%c[2J%cPpW(I3);SA[0,0][799,479];S(I(W))S(E);S(C00;W(I(D))\n",
  832.          escape,escape);
  833.      else
  834.        fprintf(plotfile,
  835.            "%c[2J%cPpW(I3);S(A[0,0][799,479]);S(I(W))S(E);S(C0);W(I(D))\n",
  836.            escape,escape);
  837.     break;
  838.  
  839.   case epson:
  840.     plotfile = freopen(pltfilename,"wb",plotfile);
  841.     fprintf(plotfile, "\0333\030");
  842.     break;
  843.  
  844.   case oki:
  845.     plotfile = freopen(pltfilename,"wb",plotfile);
  846.     fprintf(plotfile, "\033%%9\020");
  847.     break;
  848.  
  849.   case citoh:
  850.     plotfile = freopen(pltfilename,"wb",plotfile);
  851.     fprintf(plotfile, "\033T16");
  852.     break;
  853.  
  854.   case toshiba: /* reopen in binary since we always need \n\r on the file */
  855.                 /* and dos in text mode puts it, but unix does not        */
  856.     plotfile = freopen(pltfilename,"wb",plotfile);
  857.     fprintf(plotfile, "\033\032I\n\r\n\r");
  858.     fprintf(plotfile, "\033L06\n\r");
  859.     break;
  860.  
  861.   case pcl:
  862.     plotfile = freopen(pltfilename,"wb",plotfile);
  863.     fprintf(plotfile, "\033&f0S");   /* Push current cursor */
  864.     if (hpresolution == 150 || hpresolution == 300)
  865.       fprintf(plotfile, "\033*t%3dR", hpresolution);
  866.     else if (hpresolution == 75)
  867.       fprintf(plotfile, "\033*t75R");
  868.     break;
  869.  
  870.   case pcx:
  871.     plotfile = freopen(pltfilename,"wb",plotfile);
  872.     fprintf(plotfile,"\012\003\001\001%c%c%c%c",0,0,0,0);
  873.   /* Manufacturer version (1 byte) version (1 byte), encoding (1 byte),
  874.      bits per pixel (1 byte), xmin (2 bytes) ymin (2 bytes),
  875.      Version */
  876.     hres = strpwide;
  877.     vres = (long)floor(yunitspercm * ysize + 0.5);
  878.     fprintf(plotfile, "%c%c", (unsigned char)lobyte(hres - 1),
  879.         (unsigned char)upbyte(hres - 1)); /* Xmax */
  880.     fprintf(plotfile, "%c%c", (unsigned char)lobyte(vres - 1),
  881.         (unsigned char)upbyte(vres - 1)); /* Ymax */
  882.     fprintf(plotfile, "%c%c", (unsigned char)lobyte(hres),
  883.         (unsigned char)upbyte(hres));
  884.     /* Horizontal resolution */
  885.     fprintf(plotfile, "%c%c", (unsigned char)lobyte(vres),
  886.         (unsigned char)upbyte(vres));
  887.     /* Vertical resolution */
  888.     for (i = 1; i <= 48; i++)  /* fill color map with 0 */
  889.       putc('\000', plotfile);
  890.     putc('\000', plotfile);
  891.     putc('\001', plotfile);   /* Num Planes */
  892.     putc(hres / 8, plotfile);   /* Bytes per line */
  893.     putc('\000',plotfile);
  894.     for (i = 1; i <= 60; i++)   /* Filler */
  895.       putc('\000',plotfile);
  896.     break;
  897.   case fig:
  898.     fprintf(plotfile, "#FIG 2.0\n");
  899.     fprintf(plotfile, "80 2\n");
  900.     break;
  901.   case other:
  902.     break;
  903.     /* initialization code for a new plotter goes here */
  904.   }
  905. }  /* initplotter */
  906.  
  907.  
  908.  
  909.  
  910. void finishplotter()
  911. {
  912. char trash;
  913.   switch (plotter) {
  914.  
  915.   case tek:
  916.     if (previewing) {
  917.       scanf("%c%*[^\n]", &trash);
  918.       trash=getchar();
  919.       printf("%c\f", escape);
  920.     } else {
  921.       putc('\n', plotfile);
  922.       plot(penup, 1.0, 1.0);
  923.     }
  924.     break;
  925.  
  926.   case hp:
  927.     plot(penup, 1.0, 1.0);
  928.     fprintf(plotfile, "SP;\n");
  929.     break;
  930.  
  931. #ifndef MAC
  932.   case ray:
  933.     fprintf(plotfile,"end\n\nobject treecolor tree\n");
  934.     fprintf(plotfile,"object namecolor species_names\n");
  935.     break;
  936. #endif
  937.  
  938.   case pict:
  939. #if 1
  940.     fprintf(plotfile,"%c%c%c%c%c",0xa0,0x00,0x82,0xff,0x00);
  941.     bytewrite+=5;
  942.     fseek(plotfile,512L,SEEK_SET);
  943.     pictoutint(plotfile,bytewrite);
  944.     break;
  945. #else
  946.     fprintf(plotfile,"%c%c%c",0,131,255);
  947. #endif
  948.     break;
  949.  
  950.   case lw:
  951.     fprintf(plotfile, "stroke showpage \n\n");
  952.     break;
  953.  
  954.   case ibmpc:
  955. #ifdef TURBOC
  956.     trash=getchar();
  957.     restorecrtmode();
  958. #endif
  959. #ifdef QUICKC
  960.     trash=getchar();
  961.     _clearscreen(_GCLEARSCREEN);
  962.     _setvideomode(_DEFAULTMODE);
  963. #endif
  964.     break;
  965.  
  966.   case mac:
  967. #if defined(MAC) || defined(__MWERKS__) 
  968.     if (previewing) {
  969.       scanf("%c%*[^\n]", &trash);
  970.       trash=getchar();
  971. #ifdef MAC
  972.       textmode();
  973. #endif
  974.       }
  975. #endif
  976.     break;
  977.  
  978.   case houston:
  979.     break;
  980.  
  981.   case decregis:
  982.     plot(penup, 1.0, 1.0);
  983.     if (previewing)
  984.       printf("%c\\", escape);
  985.     else
  986.       fprintf(plotfile, "%c\\", escape);
  987.     if (previewing) {
  988.       trash = getchar();
  989.       printf("%c[2J",escape);
  990.     }
  991.     
  992.     break;
  993.  
  994.   case epson:
  995.     fprintf(plotfile, "\0333$");
  996.     break;
  997.  
  998.   case oki:
  999.     /* blank case */
  1000.     break;
  1001.  
  1002.   case citoh:
  1003.     fprintf(plotfile, "\033A");
  1004.     break;
  1005.  
  1006.   case toshiba:
  1007.     fprintf(plotfile, "\033\032I\n\r");
  1008.     break;
  1009.  
  1010.   case pcl:
  1011.     fprintf(plotfile, "\033&f1S");   /* pop cursor         */
  1012.     fprintf(plotfile, "\033*rB");    /* Exit graphics mode */
  1013.     putc('\f', plotfile);            /* just to make sure? */
  1014.     break;
  1015.  
  1016.   case pcx:
  1017.     /* blank case */
  1018.     break;
  1019.  
  1020.   case xbm:
  1021.     fprintf(plotfile, "}\n");
  1022.     break;
  1023.  
  1024.   case fig:
  1025.     /* blank case */
  1026.     break;
  1027.   case other:
  1028.     break;
  1029.     /* termination code for a new plotter goes here */
  1030.   }
  1031. }  /* finishplotter */
  1032.  
  1033.  
  1034. Local long SFactor()
  1035. {
  1036.   /* the dot-skip is resolution-independent. */
  1037.   /* this makes all the point-skip instructions skip the same # of dots. */
  1038.   long Result;
  1039.  
  1040.   if (hpresolution == 150)
  1041.     Result = 2;
  1042.   if (hpresolution == 300)
  1043.     Result = 1;
  1044.   if (hpresolution == 75)
  1045.     return 4;
  1046.   return Result;
  1047. }  /* SFactor */
  1048.  
  1049. long DigitsInt(x)
  1050. long x;
  1051. {
  1052.   if (x < 10)
  1053.     return 1;
  1054.   else if (x >= 10 && x < 100)
  1055.     return 2;
  1056.   else
  1057.     return 3;
  1058. }  /* DigistInt */
  1059.  
  1060. Local boolean IsColumnEmpty(mystripe, pos,deep)
  1061. striparray *mystripe;
  1062.  long pos,deep;
  1063. {
  1064.   long j;
  1065.   boolean ok;
  1066.  
  1067.   ok = true;
  1068.   j = 1;
  1069.   while (ok && j <= deep) {
  1070.     ok = (ok && mystripe[j - 1][pos - 1] == null);
  1071.     j++;
  1072.   }
  1073.   return ok;
  1074. }  /* IsColumnEmpty */
  1075.  
  1076. void Skip(Amount)
  1077.  long Amount;
  1078. {
  1079.   /* assume we're not in gfx mode. */
  1080.   fprintf(plotfile, "\033&f1S");   /* Pop the graphics cursor    */
  1081. #ifdef MAC
  1082.   fprintf(plotfile, "\033*p+%*ldX",
  1083.       (int)DigitsInt(Amount * SFactor()), Amount * SFactor());
  1084. #else
  1085.   fprintf(plotfile, "\033*p+%*dX",
  1086.       (int)DigitsInt(Amount * SFactor()), Amount * SFactor());
  1087. #endif
  1088.   fprintf(plotfile, "\033&f0S");   /* Push the cursor to new location */
  1089.   filesize += 15 + DigitsInt(Amount * SFactor());
  1090. }  /* Skip */
  1091.  
  1092. Local long FirstBlack(mystripe, startpos,deep)
  1093. striparray *mystripe;
  1094.  long startpos,deep;
  1095. {
  1096.   /* returns, given a strip and a position, next x with some y's nonzero */
  1097.   long i;
  1098.   boolean columnempty;
  1099.  
  1100.   i = startpos;
  1101.   columnempty = true;
  1102.   while (columnempty && i < strpwide / 8) {
  1103.     columnempty = (columnempty && IsColumnEmpty(mystripe, i,deep));
  1104.     if (columnempty)
  1105.       i++;
  1106.   }
  1107.   return i;
  1108. }  /* FirstBlack */
  1109.  
  1110. Local long FirstWhite(mystripe, startpos,deep)
  1111. striparray *mystripe;
  1112.  long startpos,deep;
  1113. {
  1114.   /* returns, given a strip and a position, the next x with all y's zero */
  1115.   long i;
  1116.   boolean columnempty;
  1117.  
  1118.   i = startpos;
  1119.   columnempty = false;
  1120.   while (!columnempty && i < strpwide / 8) {
  1121.     columnempty = IsColumnEmpty(mystripe, i,deep);
  1122.     if (!columnempty)
  1123.       i++;
  1124.   }
  1125.   return i;
  1126. }  /* FirstWhite */
  1127.  
  1128. Local boolean IsBlankStrip(mystripe,deep)
  1129. striparray *mystripe;
  1130.  long deep;
  1131. {
  1132.   long i, j;
  1133.   boolean ok;
  1134.  
  1135.   ok = true;
  1136.   i = 1;
  1137.   while (ok && i <= strpwide / 8) {
  1138.     for (j = 0; j < (deep); j++)
  1139.       ok = (ok && mystripe[j][i - 1] == '\0');
  1140.     i++;
  1141.   }
  1142.   return ok;
  1143. }  /* IsBlankStrip */
  1144.  
  1145.  
  1146. void striprint(div,deep)
  1147.  long div,deep;
  1148. {
  1149.   long i, j, t, x, theend, width;
  1150.   Char counter;
  1151.   boolean done;
  1152.   done = false;
  1153.   width = strpwide;
  1154.   if (plotter != pcx && plotter != pcl) {
  1155.     while (!done) {
  1156.       for (i = 0; i < div; i++)
  1157.         done = (done || (stripe[i] && stripe[i][width - 1] != null));
  1158.       if (!done)
  1159.         width--;
  1160.       done = (done || width == 0);
  1161.     }
  1162.   }
  1163.   switch (plotter) {
  1164.  
  1165.   case epson:
  1166.     if (!empty) {
  1167.       fprintf(plotfile, "\033L%c%c", width & 255, width / 256);
  1168.       for (i = 0; i < width; i++)
  1169.         putc(stripe[0][i], plotfile);
  1170.       filesize += width + 4;
  1171.     }
  1172.     putc('\n', plotfile);
  1173.     putc('\r', plotfile);
  1174.     break;
  1175.  
  1176.   case oki:
  1177.     if (!empty) {
  1178.       fprintf(plotfile, "\033%%1%c%c", width / 128, width & 127);
  1179.       for (i = 0; i < width; i++)
  1180.         putc(stripe[0][i], plotfile);
  1181.       filesize += width + 5;
  1182.     }
  1183.     putc('\n', plotfile);
  1184.     putc('\r', plotfile);
  1185.     break;
  1186.  
  1187.   case citoh:
  1188.     if (!empty) {
  1189.       fprintf(plotfile, "\033S%04d",width);
  1190.       for (i = 0; i < width; i++)
  1191.         putc(stripe[0][i], plotfile);
  1192.       filesize += width + 6;
  1193.     }
  1194.  
  1195.     putc('\n', plotfile);
  1196.     putc('\r', plotfile);
  1197.     break;
  1198.  
  1199.   case toshiba:
  1200.     if (!empty) {
  1201.       for (i = 0; i < width; i++) {
  1202.         for (j = 0; j <= 3; j++)
  1203.           stripe[j][i] += 64;
  1204.       }
  1205.       fprintf(plotfile, "\033;%04d",width);
  1206.  
  1207.       for (i = 0; i < width; i++)
  1208.         fprintf(plotfile, "%c%c%c%c",
  1209.                 stripe[0][i], stripe[1][i], stripe[2][i], stripe[3][i]);
  1210.       filesize += width * 4 + 6;
  1211.     }
  1212.     putc('\n', plotfile);
  1213.     putc('\r', plotfile);
  1214.     break;
  1215.  
  1216.   case pcx:
  1217.     width = strpwide / 8;
  1218.     for (j = 0; j < div; j++) {
  1219.       t = 1;
  1220.       while (1) {
  1221.         i = 0; /* i == RLE count ???? */
  1222.         while ((stripe[j][t + i - 1]) == (stripe[j][t + i])
  1223.                && t + i < width && i < 63)
  1224.           i++;
  1225.         if (i > 0) {
  1226.           counter = 192;
  1227.           counter += i;
  1228.           putc(counter, plotfile);
  1229.           putc(255 - stripe[j][t - 1], plotfile);
  1230.           t += i;
  1231.           filesize += 2;
  1232.         } else {
  1233.           if (255 - (stripe[j][t - 1] & 255) >= 192) {
  1234.             putc(193, plotfile);
  1235.             filesize++;
  1236.           }
  1237.           putc(255 - stripe[j][t - 1], plotfile);
  1238.           t++;
  1239.           filesize++;
  1240.  
  1241.         }
  1242.         if (t >width) break;
  1243.       }
  1244.     }
  1245.     break;
  1246.  
  1247.   case pcl:
  1248.     width = strpwide / 8;
  1249.     if (IsBlankStrip(stripe,deep)) {
  1250. #ifdef MAC
  1251.       fprintf(plotfile, "\033&f1S\033*p0X\033*p+%*ldY\033&f0S",
  1252.           (int)DigitsInt(deep * SFactor()), deep * SFactor());
  1253. #else
  1254.       fprintf(plotfile, "\033&f1S\033*p0X\033*p+%*dY\033&f0S",
  1255.           (int)DigitsInt(deep * SFactor()), deep * SFactor());
  1256. #endif
  1257.       filesize += 20 + DigitsInt(deep * SFactor());
  1258.     } else {  /* plotting the actual strip as bitmap data */
  1259.       x = 1;
  1260.       theend = 1;
  1261.       while (x < width) {
  1262.         x = FirstBlack(stripe, x,deep);    /* all-black strip is now    */
  1263.         Skip((x - theend - 1) * 8);        /* x..theend                 */
  1264.         theend = FirstWhite(stripe, x,deep) - 1;/* like lastblack            */
  1265.         fprintf(plotfile, "\033*r1A");     /* enter gfx mode            */
  1266.         for (j = 0; j < div; j++) {
  1267. #ifdef MAC
  1268.       fprintf(plotfile, "\033*b%*ldW",
  1269.           (int)DigitsInt(theend - x + 1), theend - x + 1);
  1270. #else
  1271.       fprintf(plotfile, "\033*b%*dW",
  1272.                   (int)DigitsInt(theend - x + 1), theend - x + 1);
  1273. #endif
  1274.               /* dump theend-x+1 bytes */
  1275.           for (t = x - 1; t < theend; t++)
  1276.             putc(stripe[j][t], plotfile);
  1277.           filesize += theend - x + DigitsInt(theend - x + 1) + 5;
  1278.         }
  1279.         fprintf(plotfile, "\033*rB");   /* end gfx mode */
  1280.         Skip((theend - x + 1) * 8);
  1281.         filesize += 9;
  1282.         x = theend + 1;
  1283.       }
  1284.       fprintf(plotfile, "\033&f1S");   /* Pop cursor  */
  1285. #ifdef MAC
  1286.       fprintf(plotfile, "\033*p0X\033*p+%*ldY",
  1287.           (int)DigitsInt(deep * SFactor()), deep * SFactor());
  1288. #else
  1289.       fprintf(plotfile, "\033*p0X\033*p+%*dY",
  1290.           (int)DigitsInt(deep * SFactor()), deep * SFactor());
  1291. #endif
  1292.       filesize += 20 + DigitsInt(deep * SFactor());
  1293.       fprintf(plotfile, "\033&f0S");   /* Push cursor  */
  1294.     }
  1295.     break;
  1296.     /* case for hpcl code */
  1297.   case xbm:
  1298.     x = 0;   /* count up # of bytes so we can put returns. */
  1299.     width = ((strpwide -1) / 8) +1;
  1300.     for (j = 0; j <  div; j++) {
  1301.       for (i = 0; i < width; i++) {
  1302.         fprintf(plotfile, "0x%02x,",(unsigned char)stripe[j][i]);
  1303.         filesize += 5;
  1304.         x++;
  1305.         if ((x % 15) == 0) {
  1306.           putc('\n', plotfile);
  1307.           filesize++;
  1308.         }
  1309.       }
  1310.     }
  1311.    putc('\n',plotfile);
  1312.    break;
  1313.  
  1314.   case other:
  1315.     break;
  1316.     /* graphics print code for a new printer goes here */
  1317.   }
  1318.  }  /* striprint */
  1319.  
  1320. #ifdef QUICKC
  1321. void setupgraphics()
  1322. {
  1323. _getvideoconfig(&myscreen);
  1324. #ifndef WATCOM
  1325. switch(myscreen.adapter){
  1326.   case _CGA:
  1327.   case _OCGA:
  1328.    _setvideomode(_HRESBW);
  1329.     break;
  1330.   case _EGA:
  1331.   case _OEGA:
  1332.     _setvideomode(_ERESNOCOLOR);
  1333.   case _VGA:
  1334.   case _OVGA:
  1335.   case _MCGA:
  1336.     _setvideomode(_VRES2COLOR);
  1337.      break;
  1338.   case _HGC:
  1339.     _setvideomode(_HERCMONO);
  1340.      break;
  1341.   default:
  1342.      printf("Your display hardware is unsupported by this program.\n");
  1343.       break;
  1344. }
  1345. #else
  1346. switch(myscreen.adapter){
  1347.   case _VGA:
  1348.   case _SVGA:
  1349.       _setvideomode(_VRES16COLOR);
  1350.       break;
  1351.   case _MCGA:
  1352.       _setvideomode(_MRES256COLOR);
  1353.       break;
  1354.   case _EGA:
  1355.      _setvideomode(_ERESNOCOLOR);
  1356.      break;
  1357.   case _CGA:
  1358.      _setvideomode(_MRES4COLOR);
  1359.      break;
  1360.   case _HERCULES:
  1361.      _setvideomode(_HERCMONO);
  1362.      break;
  1363.   default:
  1364.      printf("Your display hardware is unsupported by this program.\n");
  1365.      exit(-1);
  1366.      break;
  1367.    }
  1368. #endif
  1369. _getvideoconfig(&myscreen);
  1370. _setlinestyle(0xffff);
  1371. xunitspercm=myscreen.numxpixels / 25;
  1372. yunitspercm=myscreen.numypixels / 17.5;
  1373. xsize = 25.0;
  1374. ysize = 17.5;
  1375. }
  1376. #endif
  1377.  
  1378. void loadfont(font,application)
  1379. short *font;
  1380. char *application;
  1381. {
  1382.  
  1383. FILE *fontfile;
  1384.  long i, charstart, dummy;
  1385. Char trash,ch = 'A';
  1386.   i=0;
  1387.   openfile(&fontfile,FONTFILE,"r",application,NULL);
  1388.  
  1389.   while (!(eof(fontfile) || ch == ' ')) {
  1390.     charstart = i + 1;
  1391.     fscanf(fontfile, "%c%c%hd%hd%hd", &ch, &ch, &dummy, &font[charstart + 1],
  1392.            &font[charstart + 2]);
  1393.     font[charstart] = ch;
  1394.     i = charstart + 3;
  1395.     do {
  1396.       if ((i - charstart - 3) % 10 == 0) {
  1397.         fscanf(fontfile, "%*[^\n]");
  1398.         getc(fontfile);
  1399.       }
  1400.       i++;
  1401.       fscanf(fontfile, "%hd", &font[i - 1]);
  1402.     } while (abs(font[i - 1]) < 10000);
  1403.     fscanf(fontfile, "%*[^\n]");
  1404. #ifdef MAC
  1405.     queryevent();
  1406. #endif
  1407.     getc(fontfile);
  1408.     font[charstart - 1] = i + 1;
  1409.   }
  1410.   font[charstart - 1] = 0;
  1411.  FClose(fontfile);
  1412. }  /* loadfont */
  1413.  
  1414. #ifndef MAC
  1415.  
  1416.  long  showrayparms(treecolor,namecolor,backcolor,rx,ry)
  1417.  long treecolor,namecolor,backcolor,rx,ry;
  1418. {
  1419.   long i;
  1420.   Char ch,input[32];
  1421.   long numtochange;
  1422.  
  1423.   if (previewer == tek)
  1424.     printf("%c\f", escape);
  1425.   else {
  1426.     for (i = 1; i <= 24; i++)
  1427.       putchar('\n');
  1428.   }
  1429.   printf("Settings for Rayshade file: \n\n");
  1430.   printf(" (1)               Tree color:  %.10s\n",colors[treecolor-1].name);
  1431.   printf(" (2)      Species names color:  %.10s\n",colors[namecolor-1].name);
  1432.   printf(" (3)         Background color:  %.10s\n",colors[backcolor-1].name);
  1433.   printf(" (4)               Resolution:  %2ld X %2ld\n\n",rx,ry);
  1434.  
  1435.   printf(" Do you want to accept these? (Yes or No)\n");
  1436.   for (;;) {
  1437.     printf(" Type Y or N or the number (1-4) of the one to change: \n");
  1438.     gets(input);
  1439.     numtochange=atoi(input);
  1440.     uppercase(&input[0]);
  1441.     ch=input[0];
  1442.     if (ch == 'Y' || ch == 'N' || (numtochange >= 1 && numtochange <= 4))
  1443.       break;
  1444.   }
  1445.  return (ch == 'Y') ? -1 : numtochange;
  1446. }  /* showrayparms */
  1447.  
  1448.  
  1449. void getrayparms(treecolor,namecolor,backcolor,rx,ry,numtochange)
  1450.  long *treecolor,*namecolor,*backcolor,*rx,*ry;
  1451.  long numtochange;
  1452. {
  1453.   Char ch;
  1454.   long i;
  1455.  
  1456.   if (numtochange == 0) {
  1457.     do {
  1458.       printf(" Type the number of one that you want to change (1-4):\n");
  1459.       scanf("%ld%*[^\n]", &numtochange);
  1460.       getchar();
  1461.     } while (numtochange < 1 || numtochange > 10);
  1462.   }
  1463.   switch (numtochange) {
  1464.  
  1465.   case 1:
  1466.     printf("\nWhich of these colors will the tree be?:\n");
  1467.     printf("   White, Red, Orange, Yellow, Green, Blue, or Violet\n");
  1468.     printf(" (W, R, O, Y, G, B, or V)\n");
  1469.     do {
  1470.       printf(" Choose one: \n");
  1471.       scanf("%c%*[^\n]", &ch);
  1472.       getchar();
  1473.       if (ch == '\n')
  1474.         ch = ' ';
  1475.       uppercase(&ch);
  1476.       (*treecolor) = 0;
  1477.       for (i = 1; i <= 7; i++) {
  1478.         if (ch == colors[i - 1].name[0]) {
  1479.           (*treecolor) = i;
  1480.           return;
  1481.         }
  1482.       }
  1483.     } while ((*treecolor) == 0);
  1484.     break;
  1485.  
  1486.   case 2:
  1487.     printf("\nWhich of these colors will the species names be?:\n");
  1488.     printf("   White, Red, Orange, Yellow, Green, Blue, or Violet\n");
  1489.     printf(" (W, R, O, Y, G, B, or V)\n");
  1490.     do {
  1491.       printf(" Choose one: \n");
  1492.       scanf("%c%*[^\n]", &ch);
  1493.       getchar();
  1494.       if (ch == '\n')
  1495.         ch = ' ';
  1496.       uppercase(&ch);
  1497.       (*namecolor) = 0;
  1498.       for (i = 1; i <= 7; i++) {
  1499.         if (ch == colors[i - 1].name[0]) {
  1500.           (*namecolor) = i;
  1501.           return;
  1502.         }
  1503.       }
  1504.     } while ((*namecolor) == 0);
  1505.     break;
  1506.  
  1507.   case 3:
  1508.     printf("\nWhich of these colors will the background be?:\n");
  1509.     printf("   White, Red, Orange, Yellow, Green, Blue, or Violet\n");
  1510.     printf(" (W, R, O, Y, G, B, or V)\n");
  1511.     do {
  1512.       printf(" Choose one: \n");
  1513.       scanf("%c%*[^\n]", &ch);
  1514.       getchar();
  1515.       if (ch == '\n')
  1516.         ch = ' ';
  1517.       uppercase(&ch);
  1518.       (*backcolor) = 0;
  1519.       for (i = 1; i <= 7; i++) {
  1520.         if (ch == colors[i - 1].name[0]) {
  1521.           (*backcolor) = i;
  1522.           return;
  1523.         }
  1524.       }
  1525.     } while ((*backcolor) == 0);
  1526.     break;
  1527.  
  1528.   case 4:
  1529.     printf("\nEnter the X resolution:\n");
  1530.     scanf("%ld%*[^\n]", rx);
  1531.     getchar();
  1532.     printf("Enter the Y resolution:\n");
  1533.     scanf("%ld%*[^\n]",ry);
  1534.     getchar();
  1535.     break;
  1536.   }
  1537. }  /* getrayparms */
  1538.  
  1539. #endif
  1540.  
  1541. void plotrparms()
  1542. {
  1543.   /* set up initial characteristics of plotter or printer */
  1544.   Char trash,ch;                       /* colors is declared globally */
  1545.   long treecolor, namecolor, backcolor, i, rayresx, rayresy;
  1546.   double viewangle;
  1547.   long n;
  1548.  
  1549.   penchange = no;
  1550.   xcorner = 0.0;
  1551.   ycorner = 0.0;
  1552.   if (dotmatrix && (!previewing))
  1553.     strpdiv = 1;
  1554.   switch (plotter) {
  1555. #ifndef MAC
  1556.   case ray:
  1557.     penchange = yes;
  1558.     xunitspercm = 1.0;
  1559.     yunitspercm = 1.0;
  1560.     xsize = 10.0;
  1561.     ysize = 10.0;
  1562.     rayresx = 512;
  1563.     rayresy = 512;
  1564.     treecolor = 6;
  1565.     namecolor = 4;
  1566.     backcolor = 1;
  1567.     do {
  1568.       n=showrayparms(treecolor,namecolor,backcolor,rayresx,rayresy);
  1569.       if (n != -1)
  1570.         getrayparms(&treecolor,&namecolor,&backcolor,&rayresx,&rayresy,n);
  1571.     } while (n != -1);
  1572.     xsize = rayresx;
  1573.     ysize = rayresy;
  1574.  
  1575.     fprintf(plotfile, "report verbose\n");
  1576.  
  1577.     fprintf(plotfile, "screen %ld %ld\n", rayresx, rayresy);
  1578.     if (ysize >= xsize) {
  1579.       viewangle = 2 * atan(ysize / (2 * 1.21 * xsize)) * 180 / pi;
  1580.       fprintf(plotfile, "fov 45 %3.1f\n", viewangle);
  1581.       fprintf(plotfile, "light 1 point 0 %6.2f %6.2f\n",
  1582.               -xsize * 1.8, xsize * 1.5);
  1583.       fprintf(plotfile, "eyep %6.2f %6.2f %6.2f\n",
  1584.               xsize * 0.5, -xsize * 1.21, ysize * 0.55);
  1585.     } else {
  1586.       viewangle = 2 * atan(xsize / (2 * 1.21 * ysize)) * 180 / pi;
  1587.       fprintf(plotfile, "fov %3.1f 45\n", viewangle);
  1588.       fprintf(plotfile, "light 1 point 0 %6.2f %6.2f\n",
  1589.               -ysize * 1.8, ysize * 1.5);
  1590.       fprintf(plotfile, "eyep %6.2f %6.2f %6.2f\n",
  1591.               xsize * 0.5, -ysize * 1.21, ysize * 0.55);
  1592.     }
  1593.  
  1594.     fprintf(plotfile, "lookp %6.2f 0 %6.2f\n", xsize * 0.5, ysize * 0.5);
  1595.     fprintf(plotfile, "/* %.10s */\n", colors[treecolor - 1].name);
  1596.     fprintf(plotfile,
  1597.             "surface treecolor diffuse %5.2f%5.2f%5.2f specular 1 1 1 specpow 30\n",
  1598.             colors[treecolor - 1].red, colors[treecolor - 1].green,
  1599.             colors[treecolor - 1].blue);
  1600.     fprintf(plotfile, "/* %.10s */\n", colors[namecolor - 1].name);
  1601.     fprintf(plotfile,
  1602.             "surface namecolor diffuse %5.2f%5.2f%5.2f specular 1 1 1 specpow 30\n",
  1603.             colors[namecolor - 1].red, colors[namecolor - 1].green,
  1604.             colors[namecolor - 1].blue);
  1605.     fprintf(plotfile, "/* %.10s */\n", colors[backcolor - 1].name);
  1606.     fprintf(plotfile, "surface backcolor diffuse %5.2f%5.2f%5.2f\n\n",
  1607.             colors[backcolor - 1].red, colors[backcolor - 1].green,
  1608.             colors[backcolor - 1].blue);
  1609.     break;
  1610. #endif /* ifndef mac */
  1611.   case pict:
  1612.     penchange = yes;
  1613.     xunitspercm = 28.346456693;
  1614.     yunitspercm = 28.346456693;
  1615.     /*7.5 x 10 inch default PICT page size*/
  1616.     xsize = 19.05;
  1617.     ysize = 25.40;
  1618.     break;
  1619.  
  1620.   case lw:
  1621.     penchange = yes;
  1622.     xunitspercm = 28.346456693;
  1623.     yunitspercm = 28.346456693;
  1624.     xsize = 21.59;
  1625.     ysize = 27.94;
  1626.     break;
  1627.  
  1628.   case hp:
  1629.     penchange = yes;
  1630.     xunitspercm = 400.0;
  1631.     yunitspercm = 400.0;
  1632.     xsize = 24.0;
  1633.     ysize = 18.0;
  1634.     break;
  1635.  
  1636.   case tek:
  1637.     xunitspercm = 50.0;
  1638.     yunitspercm = 50.0;
  1639.     xsize = 20.46;
  1640.     ysize = 15.6;
  1641.     break;
  1642.  
  1643.   case ibmpc:
  1644. #ifdef TURBOC
  1645.   GraphDriver = 0;
  1646.   detectgraph(&GraphDriver,&GraphMode);
  1647.   getmoderange(GraphDriver,&LoMode,&HiMode);
  1648.   initgraph(&GraphDriver,&HiMode,"");
  1649.   xunitspercm = getmaxx()/25;
  1650.   yunitspercm = getmaxy() / 17.5;
  1651.   restorecrtmode();
  1652.   xsize = 25.0;
  1653.   ysize = 17.5;
  1654. #endif
  1655. #ifdef QUICKC
  1656. setupgraphics();
  1657.  
  1658. #endif
  1659.   break;
  1660.  
  1661.   case mac:
  1662.     penchange = yes;
  1663.     xunitspercm = 33.5958;
  1664.     yunitspercm = 33.6624;
  1665.     xsize = 15.24;
  1666.     ysize = 10.00;
  1667.     break;
  1668.  
  1669.   case houston:
  1670.     penchange = yes;
  1671.     xunitspercm = 100.0;
  1672.     yunitspercm = 100.0;
  1673.     xsize = 24.5;
  1674.     ysize = 17.5;
  1675.     break;
  1676.  
  1677.   case decregis:
  1678.     xunitspercm = 30.0;
  1679.     yunitspercm = 30.0;
  1680.     xsize = 25.0;
  1681.     ysize = 15.0;
  1682.     break;
  1683.  
  1684.   case epson:
  1685.     penchange = yes;
  1686.     xunitspercm = 47.244;
  1687.     yunitspercm = 28.346;
  1688.     xsize = 18.70;
  1689.     ysize = 22.0;
  1690.     strpwide = 960;
  1691.     strpdeep = 8;
  1692.     strpdiv = 1;
  1693.     break;
  1694.  
  1695.   case oki:
  1696.     penchange = yes;
  1697.     xunitspercm = 56.692;
  1698.     yunitspercm = 28.346;
  1699.     xsize = 19.0;
  1700.     ysize = 22.0;
  1701.     strpwide = 1100;
  1702.     strpdeep = 8;
  1703.     strpdiv = 1;
  1704.     break;
  1705.  
  1706.   case citoh:
  1707.     penchange = yes;
  1708.     xunitspercm = 28.346;
  1709.     yunitspercm = 28.346;
  1710.     xsize = 22.3;
  1711.     ysize = 26.0;
  1712.     strpwide = 640;
  1713.     strpdeep = 8;
  1714.     strpdiv = 1;
  1715.     break;
  1716.  
  1717.   case toshiba:
  1718.     penchange = yes;
  1719.     xunitspercm = 70.866;
  1720.     yunitspercm = 70.866;
  1721.     xsize = 19.0;
  1722.     ysize = 25.0;
  1723.     strpwide = 1350;
  1724.     strpdeep = 24;
  1725.     strpdiv = 4;
  1726.     break;
  1727.  
  1728.   case pcl:
  1729.     penchange = yes;
  1730.     xsize = 21.59;
  1731.     ysize = 27.94;
  1732.     xunitspercm = 118.11023622;   /* 300 DPI = 118.1 DPC                    */
  1733.     yunitspercm = 118.11023622;
  1734.     strpwide = 2550;   /* 8.5 * 300 DPI                                     */
  1735.     strpdeep = 20;     /* height of the strip                               */
  1736.     strpdiv = 20;      /* in this case == strpdeep                          */
  1737.                        /* this is information for 300 DPI resolution        */
  1738.     printf("Please select Laserjet resolution\n\n");
  1739.     printf("1:  75 DPI\n2:  150 DPI\n3:  300 DPI\n\n");
  1740.     do {
  1741.       scanf("%c%*[^\n]", &ch);
  1742.       trash=getchar();
  1743.       uppercase(&ch);
  1744.     } while (ch != '1' && ch != '2' && ch != '3');
  1745.     switch (ch) {
  1746.  
  1747.     case '1':
  1748.       strpwide /= 4;
  1749.       xunitspercm /= 4.0;
  1750.       yunitspercm /= 4.0;
  1751.       hpresolution = 75;
  1752.       break;
  1753.  
  1754.     case '2':
  1755.       strpwide /= 2;
  1756.       xunitspercm /= 2.0;
  1757.       yunitspercm /= 2.0;
  1758.       hpresolution = 150;
  1759.       break;
  1760.  
  1761.     case '3':
  1762.       hpresolution = 300;
  1763.       break;
  1764.     }
  1765.     break;
  1766.   case xbm:            /* since it's resolution dependent, make 1x1 pixels  */
  1767.     penchange = yes;   /* per square cm for easier math.                    */
  1768.     xunitspercm = 1.0;
  1769.     yunitspercm = 1.0;
  1770.     strpdeep = 10;
  1771.     strpdiv = 10;
  1772.     printf("Please select the X-bitmap file resolution\n");
  1773.     printf("X resolution?\n");
  1774.     scanf("%lf%*[^\n]", &xsize);
  1775.     getchar();
  1776.     printf("Y resolution?\n");
  1777.     scanf("%lf%*[^\n]", &ysize);
  1778.     getchar();
  1779.     strpwide = (long)xsize;
  1780.     xsize /= xunitspercm;
  1781.     ysize /= yunitspercm;
  1782.  
  1783.     break;
  1784.  
  1785.   case pcx:
  1786.     penchange = yes;
  1787.     xsize = 21.16;
  1788.     ysize = 15.88;
  1789.     strpdeep = 10;
  1790.     strpdiv = 10;
  1791.     printf("Please select the PCX file resolution\n\n");
  1792.     printf("1: EGA 640  X 350\n");
  1793.     printf("2: VGA 800  X 600\n");
  1794.     printf("3: VGA 1024 X 768\n\n");
  1795.     do {
  1796.       scanf("%c%*[^\n]", &ch);
  1797.       trash=getchar();
  1798.       uppercase(&ch);
  1799.     } while (ch != '1' && ch != '2' && ch != '3');
  1800.     switch (ch) {
  1801.  
  1802.     case '1':
  1803.       strpwide = 640;
  1804.       yunitspercm = 350 / ysize;
  1805.       break;
  1806.  
  1807.     case '2':
  1808.       strpwide = 800;
  1809.       yunitspercm = 600 / ysize;
  1810.       break;
  1811.  
  1812.     case '3':
  1813.       strpwide = 1024;
  1814.       yunitspercm = 768 / ysize;
  1815.       break;
  1816.     }
  1817.     xunitspercm = strpwide / xsize;
  1818.     break;
  1819.   case fig:
  1820.     penchange = yes;
  1821.     xunitspercm = 31.011;
  1822.     yunitspercm = 29.78;
  1823.     xsize = 25.4;
  1824.     ysize = 20.32;
  1825.     break;
  1826.   case other:
  1827.     break;
  1828.     /* initial parameter settings for a new plotter go here */
  1829.   }
  1830.   if (previewing)
  1831.     return;
  1832. }  /* plotrparms */
  1833.  
  1834.  
  1835. void getplotter()
  1836. {
  1837.   Char ch,trash;
  1838.  
  1839.   printf("\nWhich plotter or printer will the tree be drawn on?\n");
  1840.   printf("(many other brands or models are compatible with these)\n\n");
  1841.   printf("   type:       to choose one compatible with:\n\n");
  1842.   printf("        L         Apple Laserwriter (with Postscript)\n");
  1843.   printf("        M         MacDraw PICT format\n");
  1844. #ifndef MAC
  1845.   printf("        R         Rayshade 3D rendering program file\n");
  1846. #endif
  1847.   printf("        J         Hewlett-Packard Laserjet\n");
  1848.   printf("        K         TeKtronix 4010 graphics terminal\n");
  1849.   printf("        H         Hewlett-Packard 7470 plotter\n");
  1850. #ifdef DOS
  1851.   printf("        I         IBM PC graphics screens\n");
  1852. #endif
  1853.   printf("        D         DEC ReGIS graphics (VT240 terminal)\n");
  1854.   printf("        B         Houston Instruments plotter\n");
  1855.   printf("        E         Epson MX-80 dot-matrix printer\n");
  1856.   printf("        C         Prowriter/Imagewriter dot-matrix printer\n");
  1857.   printf("        O         Okidata dot-matrix printer\n");
  1858.   printf("        T         Toshiba 24-pin dot-matrix printer\n");
  1859.   printf("        P         PC Paintbrush monochrome PCX file format\n");
  1860.   printf("        X         X Bitmap format                         \n");
  1861.   printf("        F         FIG 2.0 format                          \n");
  1862.   printf("        U         other: one you have inserted code for\n");
  1863.   do {
  1864.     printf(" Choose one: \n");
  1865.     scanf("%c%*[^\n]", &ch);
  1866.     trash=getchar();
  1867.     uppercase(&ch);
  1868.   }
  1869. #ifdef DOS
  1870. while (strchr("LJKHIDBECOTUPXRMF",ch) == NULL);
  1871. #else
  1872. while (strchr("LJKHDBECOTUPXRMF",ch) == NULL);
  1873. #endif
  1874.   switch (ch) {
  1875.  
  1876.   case 'L':
  1877.     plotter = lw;
  1878.     break;
  1879.  
  1880.   case 'M':
  1881.     plotter = pict;
  1882.     break;
  1883.  
  1884.  case 'R':
  1885.     plotter = ray;
  1886.     break;
  1887.  
  1888.   case 'J':
  1889.     plotter = pcl;
  1890.     break;
  1891.  
  1892.   case 'K':
  1893.     plotter = tek;
  1894.     break;
  1895.  
  1896.   case 'H':
  1897.     plotter = hp;
  1898.     break;
  1899.  
  1900.   case 'I':
  1901.     plotter = ibmpc;
  1902.     break;
  1903.  
  1904.   case 'D':
  1905.     plotter = decregis;
  1906.     break;
  1907.  
  1908.   case 'B':
  1909.     plotter = houston;
  1910.     break;
  1911.  
  1912.   case 'E':
  1913.     plotter = epson;
  1914.     break;
  1915.  
  1916.   case 'C':
  1917.     plotter = citoh;
  1918.     break;
  1919.  
  1920.   case 'O':
  1921.     plotter = oki;
  1922.     break;
  1923.  
  1924.   case 'T':
  1925.     plotter = toshiba;
  1926.     break;
  1927.  
  1928.   case 'P':
  1929.     plotter = pcx;
  1930.     break;
  1931.  
  1932.   case 'X':
  1933.     plotter = xbm;
  1934.     break;
  1935.  
  1936.   case 'F':
  1937.     plotter = fig;
  1938.     break;
  1939.  
  1940.   case 'U':
  1941.     plotter = other;
  1942.     break;
  1943.   }
  1944.   dotmatrix = (plotter == epson || plotter == oki || plotter == citoh ||
  1945.                plotter == toshiba || plotter == pcx || plotter == pcl ||
  1946.                plotter == xbm);
  1947.   printf("\nWhich type of screen will it be previewed on?\n\n");
  1948.   printf("   type:       to choose one compatible with:\n\n");
  1949.   printf("        N         will not be previewed\n");
  1950. #ifdef DOS
  1951.   printf("        I         IBM PC graphics screens\n");
  1952. #else
  1953. #if defined(MAC) || defined(__MWERKS__)
  1954.   printf("        M         Macintosh screens\n");
  1955. # else
  1956.   printf("        K         TeKtronix 4010 graphics terminal\n");
  1957.   printf("        D         DEC ReGIS graphics (VT240 terminal)\n");
  1958.   printf("        U         other: one you have inserted code for\n");
  1959. # endif
  1960. #endif
  1961.   do {
  1962.     printf(" Choose one: \n");
  1963.     scanf("%c%*[^\n]", &ch);
  1964.     trash=getchar();
  1965.     uppercase(&ch);
  1966.   }
  1967. #ifdef DOS
  1968.   while (strchr("NIKDU",ch) == NULL);
  1969. #else
  1970. #if defined(MAC) || defined(__MWERKS__)
  1971.   while (strchr("NMKDU",ch) == NULL);
  1972. #  else
  1973.   while (strchr("NKDU",ch) == NULL);
  1974. #  endif
  1975. #endif
  1976.   preview = true;
  1977.   switch (ch) {
  1978.  
  1979.   case 'N':
  1980.     preview = false;
  1981.     break;
  1982.  
  1983.   case 'I':
  1984.     previewer = ibmpc;
  1985.     break;
  1986.  
  1987.   case 'M':
  1988.     previewer = mac;
  1989.     break;
  1990.  
  1991.   case 'K':
  1992.     previewer = tek;
  1993.     break;
  1994.  
  1995.   case 'D':
  1996.     previewer = decregis;
  1997.     break;
  1998.  
  1999.   case 'U':
  2000.     previewer = other;
  2001.     break;
  2002.   }
  2003.   printf("\n\n\n");
  2004. }  /* getplotter */
  2005.  
  2006.  
  2007. void changepen(pen)
  2008. pentype pen;
  2009. {
  2010.   Char picthi, pictlo;
  2011.   long  pictint;
  2012.  
  2013.  switch (pen) {
  2014.  
  2015.   case treepen:
  2016.     linewidth = treeline;
  2017.     if (plotter == hp)
  2018.       fprintf(plotfile, "SP1;\n");
  2019.     if (plotter == lw) {
  2020.       fprintf(plotfile, "stroke %8.2f setlinewidth \n", treeline);
  2021.       fprintf(plotfile, " 1 setlinecap 1 setlinejoin \n");
  2022.     }
  2023.     break;
  2024.  
  2025.   case labelpen:
  2026.     linewidth = labelline;
  2027.     if (plotter == hp)
  2028.       fprintf(plotfile, "SP2;\n");
  2029.     if (plotter == lw) {
  2030.       fprintf(plotfile, " stroke%8.2f setlinewidth \n", labelline);
  2031.       fprintf(plotfile, "1 setlinecap 1 setlinejoin \n");
  2032.     }
  2033.     break;
  2034.   }
  2035. #if defined(MAC) || defined(__MWERKS__)
  2036. if (plotter == mac){
  2037.       pictint = ( long)(linewidth + 0.5);
  2038.       if (pictint ==0)
  2039.            pictint = 1;
  2040.       PenSize((int)pictint,(int)pictint);}
  2041. #endif
  2042.  
  2043.   if (plotter != pict)
  2044.     return;
  2045.   pictint = ( long)(linewidth + 0.5);
  2046.   if (pictint == 0)
  2047.     pictint = 1;
  2048.   picthi = (Char)(pictint / 256);
  2049.   pictlo = (Char)(pictint & 255);
  2050.   fprintf(plotfile, "\007%c%c%c%c", picthi, pictlo, picthi, pictlo);
  2051.   bytewrite+=5;
  2052. }  /* changepen */
  2053.  
  2054.  
  2055. double lengthtext(pstring, nchars,font)
  2056. Char *pstring;
  2057.  long nchars;
  2058. fonttype font;
  2059. {  /* lengthext */
  2060.   long i, j, code;
  2061.   static double sumlength;
  2062.   sumlength = 0.0;
  2063.   for (i = 0; i < nchars; i++) {
  2064.     code = pstring[i];
  2065.     j = 1;
  2066.     while (font[j] != code && font[j - 1] != 0)
  2067.       j = font[j - 1];
  2068.     if (font[j] == code)
  2069.       sumlength += font[j + 2];
  2070.   }
  2071.   return sumlength;
  2072. }  /* lengthtext */
  2073.  
  2074.  
  2075. void plotchar(place,text)
  2076.  long *place;
  2077. struct LOC_plottext *text;         /* variables passed from plottext */
  2078. {
  2079.   text->heightfont = text->font[*place + 1];
  2080.   text->yfactor = text->height / text->heightfont;
  2081.   text->xfactor = text->yfactor;
  2082.   *place += 3;
  2083.   do {
  2084.     (*place)++;
  2085.     text->coord = text->font[*place - 1];
  2086.     if (text->coord > 0)
  2087.       text->penstatus = pendown;
  2088.     else
  2089.       text->penstatus = penup;
  2090.     text->coord = abs(text->coord);
  2091.     text->coord %= 10000;
  2092.     text->xfont = (text->coord / 100 - xstart) * text->xfactor;
  2093.     text->yfont = (text->coord % 100 - ystart) * text->yfactor;
  2094.     text->xplot = text->xx + (text->xfont * text->cosslope +
  2095.                   text->yfont * text->sinslope) * text->compress;
  2096.     text->yplot = text->yy - text->xfont * text->sinslope +
  2097.       text->yfont * text->cosslope;
  2098.     plot(text->penstatus, text->xplot, text->yplot);
  2099.   } while (abs(text->font[*place - 1]) < 10000);
  2100.   text->xx = text->xplot;
  2101.   text->yy = text->yplot;
  2102. }  /* plotchar */
  2103.  
  2104. swap(one,two)
  2105. char **one,**two;
  2106. {
  2107. char *tmp = (*one);
  2108. (*one)= (*two);
  2109. (*two) = tmp;
  2110. return;
  2111. }
  2112.  
  2113. void drawit(fontname,xoffset,yoffset,numlines,root)
  2114. char *fontname;
  2115. double *xoffset,*yoffset;
  2116.  long  numlines;
  2117. node *root;
  2118. {
  2119.   long i, j, line;
  2120.   long deep,iterations;
  2121.   (*xoffset) = 0.0;
  2122.   (*yoffset) = 0.0;
  2123.   if (dotmatrix){
  2124.     strptop    = ( long)(ysize * yunitspercm);
  2125.     strpbottom = numlines*strpdeep + 1;
  2126.   }
  2127.   else {
  2128.     plottree(root,root);
  2129.     plotlabels(fontname);
  2130.   }
  2131.   if (dotmatrix){
  2132.     striprint(( long)((ysize * yunitspercm)- (numlines * strpdeep)),
  2133.           ( long)((ysize * yunitspercm)- (numlines * strpdeep)));
  2134.     strptop = numlines * strpdeep;
  2135.     strpbottom = strptop - strpdeep + 1;
  2136.     printf(" writing%3d lines ...\n", numlines);
  2137.     printf("  Line     Output file size\n");
  2138.     printf("  ----     ------ ---- ----\n");
  2139.     for (line = 1; line <= numlines ; line++) {
  2140.       for (i = 0; i <= strpdeep ; i++){
  2141.         for (j=0; j<=(strpwide/8);++j)
  2142.       stripe[i][j] = 0;}
  2143.       empty = true;
  2144.       xnow = strpwide / 2.0;
  2145.       ynow = 0.0;
  2146.       plottree(root, root);
  2147.       plotlabels(fontname);
  2148.       strptop = strpbottom - 1;
  2149.       strpbottom -= strpdeep;
  2150.       deep=20;
  2151.       if (strpdeep > deep){              /* large stripe, do in 20-line     */
  2152.         for (i=0;i<strpdeep;++i){
  2153.       swap(&stripe[i%deep],&stripe[i]);
  2154.       if ((i%deep) == (deep -1)){
  2155.         striprint(deep,deep);}
  2156.         }
  2157.         striprint(strpdeep%deep,strpdeep%deep);
  2158.       }
  2159.       else{                          /* small stripe, do it all now.     */
  2160.         striprint(strpdiv,strpdeep);
  2161.         if (line % 5 == 0)
  2162.           printf("%5ld%16ld\n", line, filesize);
  2163.       }
  2164.     }
  2165.   }
  2166. }  /* drawit */
  2167.  
  2168.  
  2169. void plottext(pstring, nchars, height_, cmpress2, x, y, slope, font_,fontname)
  2170. Char *pstring;
  2171.  long nchars;
  2172. double height_, cmpress2, x, y, slope;
  2173. short *font_;
  2174. char *fontname;
  2175. {
  2176.   struct LOC_plottext text;
  2177.   long i, j, code;
  2178.   double pointsize;
  2179.   text.heightfont = font_[2];
  2180.  
  2181.   pointsize = (1.2*(height_/text.heightfont)*cmpress2 / 2.54) * 72.0;
  2182.   text.height = height_;
  2183.   text.compress = cmpress2;
  2184.   text.font = font_;
  2185.   text.xx = x;
  2186.   text.yy = y;
  2187.   text.sinslope = sin(pi * slope / 180.0);
  2188.   text.cosslope = cos(pi * slope / 180.0);
  2189.   if (previewing || (strcmp(fontname,"Hershey") == 0)){
  2190.     for (i = 0; i < nchars; i++) {
  2191.       code = pstring[i];
  2192.       j = 1;
  2193.       while (text.font[j] != code && text.font[j - 1] != 0)
  2194.     j = text.font[j - 1];
  2195.       plotchar(&j,  &text);
  2196.     }
  2197.   }
  2198.  
  2199.   else if (plotter == lw)  {
  2200.  /* print alternate font.  Right now, only postscript. */
  2201.     fprintf(plotfile,"gsave\n");
  2202.     fprintf(plotfile,"/%s findfont %f scalefont setfont\n",fontname,
  2203.         pointsize);
  2204.     fprintf(plotfile,"%f %f translate %f rotate\n",x,y,-slope);
  2205.     fprintf(plotfile,"0 0 moveto\n");
  2206.     fprintf(plotfile,"(%s) show\n",pstring);
  2207.     fprintf(plotfile,"grestore\n");
  2208.   }
  2209. }  /* plottext */
  2210.  
  2211.  
  2212. void makebox(fn,xo,yo,scale,ntips)
  2213. char *fn;                          /* fontname                       */
  2214. double *xo,*yo;                    /* x and y offsets                 */
  2215. double *scale;
  2216.  long ntips;
  2217. {
  2218.   /* draw the box on screen which represents plotting area.        */
  2219.   char ch;
  2220.  
  2221.   printf("\nWe now will preview the tree.  The box that will be\n");
  2222.   printf("plotted on the screen represents the boundary of the\n");
  2223.   printf("final plotting surface.  To see the preview, press on\n");
  2224.   printf("the ENTER or RETURN key (you may need to do it twice).\n");
  2225.   printf("When finished viewing it, press on that key again.\n");
  2226.   oldpenchange   = penchange;
  2227.   oldxsize       = xsize;
  2228.   oldysize       = ysize;
  2229.   oldxunitspercm = xunitspercm;
  2230.   oldyunitspercm = yunitspercm;
  2231.   oldxcorner     = xcorner;
  2232.   oldycorner     = ycorner;
  2233.   oldplotter     = plotter;
  2234.   plotter        = previewer;
  2235.   scanf("%c%*[^\n]", &ch);
  2236.   (void)getchar();
  2237.   if (ch == '\n')
  2238.     ch = ' ';
  2239.   plotrparms();
  2240.   xcorner += 0.05 * xsize;
  2241.   ycorner += 0.05 * ysize;
  2242.   xsize *= 0.9;
  2243.   ysize *= 0.9;
  2244.   (*scale) = ysize / oldysize;
  2245.   if (xsize / oldxsize < (*scale))
  2246.     (*scale) = xsize / oldxsize;
  2247.   (*xo) = (xcorner + (xsize - oldxsize * (*scale)) / 2.0) / (*scale);
  2248.   (*yo) = (ycorner   + (ysize - oldysize * (*scale)) / 2.0) / (*scale);
  2249.   xscale = (*scale) * xunitspercm;
  2250.   yscale = (*scale) * yunitspercm;
  2251.   initplotter(ntips,fn);
  2252.   plot(penup, xscale * (*xo), yscale * (*yo));
  2253.   plot(pendown, xscale * (*xo), yscale * ((*yo) + oldysize));
  2254.   plot(pendown, xscale * ((*xo) + oldxsize), yscale * ((*yo) + oldysize));
  2255.   plot(pendown, xscale * ((*xo) + oldxsize), yscale * (*yo));
  2256.   plot(pendown, xscale * (*xo), yscale * (*yo));
  2257. }  /* makebox */
  2258.  
  2259.  
  2260. boolean plotpreview(fn,xo,yo,scale,nt,root)
  2261. char *fn;        /* font name                                              */
  2262. double *xo,*yo;
  2263. double *scale;
  2264.  long nt;        /* ntips                                                  */
  2265. node *root;
  2266. {
  2267.   boolean canbeplotted;
  2268.   Char ch;
  2269.  
  2270.   previewing = true;
  2271.   makebox(fn,xo,yo,scale,nt);
  2272.   plottree(root, root);
  2273.   plotlabels(fn);
  2274.   finishplotter();
  2275.   penchange = oldpenchange;
  2276.   xsize = oldxsize;
  2277.   ysize = oldysize;
  2278.   xunitspercm = oldxunitspercm;
  2279.   yunitspercm = oldyunitspercm;
  2280.   xscale = xunitspercm;
  2281.   yscale = yunitspercm;
  2282.   plotter = oldplotter;
  2283.   xcorner = oldxcorner;
  2284.   ycorner = oldycorner;
  2285.   printf(" Is the tree ready to be plotted? (Answer Y or N)\n");
  2286.   do {
  2287.     printf("Type Y or N:\n");
  2288.     scanf("%c%*[^\n]", &ch);
  2289.     (void)getchar();
  2290.     if (ch == '\n')
  2291.       ch = ' ';
  2292.     uppercase(&ch);
  2293.   } while (ch != 'Y' && ch != 'N');
  2294.   canbeplotted = (ch == 'Y');
  2295.   return canbeplotted;
  2296. }  /* plotpreview */
  2297.  
  2298.  
  2299. long allocstripe(stripe,x,y)
  2300. striptype stripe;
  2301. long x,y;
  2302. {
  2303.   long i,stripedepth;
  2304.   for (i=0 ; i<=y;++i){
  2305.     stripe[i] = (MALLOCRETURN *)malloc((x+1)*sizeof(Char));
  2306.     if (!stripe[i])
  2307.       break;
  2308.    }
  2309. return i-1;
  2310. }
  2311.  
  2312.